#include "scene.h"
#include <math.h>
#include <QtGlobal>
#include <QtCore/qmath.h>
#include <QtCore/QVector>

int Scene::minCost(int up, int down, int left, int right)
{
    int m = qMin(qMin(up, down), qMin(left, right)), result = 0;
    if(m == up) result = 2;
    else if(m == down) result = 3;
    else if(m == left) result = 0;
    else if(m == right) result = 1;
    return result;
}

int Scene::step(const int step, int& startR, int& startC, const int orientation,
         const int finalR, const int finalC,
         const QVector<cell_state_t>& tauler)
{
    int NewRow, NewColumn;
    NewRow = startR;
    NewColumn = startC;
    switch(orientation)
    {
            case 0: NewColumn += step; break;
            case 90: NewRow += step; break;
            case 180: NewColumn -= step; break;
            case 270: NewRow -= step; break;
            default: break;
    }
    NewRow = qMax(0, qMin(NewRow, m_rows - 1));
    NewColumn = qMax(0, qMin(NewColumn, m_columns - 1));
    startR = NewRow; startC = NewColumn;
    if(NewRow == finalR && NewColumn == finalC) return 0;
    if(tauler.at(NewRow * m_columns + NewColumn) == empty)
    {
        return pathfinding(NewRow, NewColumn, orientation, finalR, finalC, tauler);
    }
    else return 3000;
}

int Scene::pathfinding(int& startR, int& startC, const int orientation, const int finalR, const int finalC, const QVector<cell_state_t>& tauler)
{
    int r, c, costUp, costDown, costLeft, costRight;
    r = startR; c = startC;
    costUp = 1 + step(1, r, c, orientation, finalR, finalC, tauler);
    if(r == finalR && c == finalC) return 2;
    if(r == startR && c == startC) costUp = 6000;
    r = startR; c = startC;
    costDown = 1 + step(-1, r, c, orientation, finalR, finalC, tauler);
    if(r == finalR && c == finalC) return 3;
    if(r == startR && c == startC) costDown = 6000;
    r = startR; c = startC;
    costLeft = 2 + step(1, r, c, (orientation + 270) % 360, finalR, finalC, tauler);
    if(r == finalR && c == finalC) return 0;
    if(r == startR && c == startC) costLeft = 6000;
    r = startR; c = startC;
    costRight = 1 + step(1, r, c, (orientation + 90) % 360, finalR, finalC, tauler);
    if(r == finalR && c == finalC) return 1;
    if(r == startR && c == startC) costRight = 6000;
    return minCost(costUp, costDown, costLeft, costRight);
}

bool Scene::MoureEnemicsPathFind()
{
    QVector<cell_state_t> tmp(m_rows * m_columns);
    bool gameover = false;
    int from = 0, id, hr, hc;
    HeroLocation(hr, hc);
    for(int i = 0; i < tmp.size(); ++i) tmp[i] = m_tauler.at(i);
    for(int i = 0; !gameover && i < m_NumBaddies; ++i)
    {
        int e = EnemyLocation(from, tmp, id);
	if(id < 0) break;
        int r = e / m_columns;
        int c = e % m_columns;
        int angle = enemiesOrtientation.at(id);
        switch(pathfinding(r,c, angle, hr, hc, m_tauler))
        {
        case 0: enemiesOrtientation[id] = (angle + 90) % 360; break;
        case 1: enemiesOrtientation[id] = (angle - 90) % 360; break;
        case 2: AdvanceCharacter(1, r, c, angle, (cell_state_t)(enemy0 + id)); break;
        case 3: AdvanceCharacter(-1, r, c, angle, (cell_state_t)(enemy0 + id)); break;
        }
        gameover = (r == hr && c == hc);
        from = e + 1;
    }
    return gameover;
}
